package com.avantis.admin.controller;

import com.alibaba.fastjson.JSON;
import com.avantis.admin.config.shiro.*;
import com.avantis.admin.service.AdminUserService;
import com.avantis.admin.service.RoleService;
import com.avantis.admin.service.UserService;
import com.avantis.admin.utils.PasswordHelper;
import com.avantis.common.base.BaseController;
import com.avantis.common.entity.AdminUser;
import com.avantis.common.entity.User;
import com.avantis.common.msg.YResult;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.*;
import org.apache.shiro.subject.Subject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.http.MediaType;
import org.springframework.util.StringUtils;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.TimeUnit;


/**
 * @ClassName UserController
 * @Description TODO
 * @Author kirago
 * @Date 2018/11/27 11:31
 * @Version 1.0
 **/
@Api(value = "用户接口", description = "用户注册，登录，登出，获取用户信息等服务")
@RestController
@RequestMapping("/user")
public class UserController extends BaseController {

    @Autowired
    protected StringRedisTemplate writeTemplate;

    private static final Logger LOGGER=LoggerFactory.getLogger(UserController.class);

    @Autowired
    private AdminUserService adminUserService;

    @ApiOperation("登录接口")
    @PostMapping(value = "/login")
    public YResult Login(@Validated @RequestBody LoginModel loginModel) {

        YResult result = restProcessor(() -> {

            Subject subject = SecurityUtils.getSubject();
            LOGGER.info("当前主体是否已认证"+subject.isAuthenticated());

            try {
                JwtToken jwtToken = new JwtToken(loginModel.getAccount().trim(), loginModel.getPassword().trim());

                subject.login(jwtToken);

                AdminUser adminUser=null;

                if(StringUtils.isEmpty(loginModel.getAccount())||StringUtils.isEmpty(loginModel.getPassword())){
                    return YResult.error("用户名密码不能为空!");
                }else{
                    String password = PasswordHelper.encryptPassword(loginModel.getAccount().trim(),loginModel.getPassword().trim());
                    adminUser = adminUserService.login(loginModel.getAccount().trim(),password);
                }
                if(adminUser==null){
                    return YResult.error("无此用户或账号密码错误!");
                }

                adminUser.setOriginalPassword(loginModel.getPassword().trim());
                String jwt = JwtUtils.sign(adminUser.getId().toString());

                writeTemplate.opsForValue().set(jwt, JSON.toJSONString(adminUser), JwtUtils.REDIS_TOKEN_EXPIRE, TimeUnit.MILLISECONDS);

                Map<String,Object> resultMap=new HashMap<>();
                resultMap.put("accessToken",jwt);
                resultMap.put("userInfo",adminUser);

                return YResult.ok(resultMap);

            } catch (UnknownAccountException exception) {
                throw exception;
            } catch (IncorrectCredentialsException exception) {
                throw exception;
            } catch (LockedAccountException exception) {
                throw exception;
            } catch (ExcessiveAttemptsException exception) {
                throw exception;
            } catch (AuthenticationException exception) {
                throw exception;
            } catch (Exception exception) {
                exception.printStackTrace();
                throw exception;
            }
        });
        return result;
    }

    @ApiOperation("登出用户")
    @PostMapping("/logout")
    public YResult logout(HttpServletRequest request) {
        YResult result = restProcessor(() -> {
            String accessToken = JwtFilter.getAccessToken(request);
            if (!StringUtils.isEmpty(accessToken)) {
                writeTemplate.delete(accessToken);
            }
            Subject subject = SecurityUtils.getSubject();
            subject.logout();
            return YResult.ok();
        });

        return result;
    }

    @ApiOperation("注册接口")
    @PostMapping("/addUser")
    public YResult addUser(@Validated @RequestBody AdminUser adminUser) {
        YResult result = restProcessor(() -> {
                adminUserService.saveAdmin(adminUser);
                return YResult.ok();
        });
        return result;
    }


}
